/* eslint-disable react-hooks/exhaustive-deps */
import React, { useRef, useState } from 'react'
import classNames from 'classnames'

export interface LoadingSpinnerProps extends React.SVGAttributes<SVGElement> {
    variant?: 'primary' | 'secondary'
}

export default function LoadingSpinner({
    variant = 'primary',
    ...rest
}: LoadingSpinnerProps): JSX.Element {
    const cyan = variant === 'primary' ? '#4CC9F0' : '#48494B'
    const blue = variant === 'primary' ? '#4361EE' : '#48494B'
    const purple = variant === 'primary' ? '#7209B7' : '#48494B'
    const pink = variant === 'primary' ? '#F72585' : '#48494B'

    const [frame, setFrame] = useState(0)

    const frameRequest = useRef<number>()
    const currentFrameStartTime = useRef<number>()

    const animate = (time: number) => {
        if (currentFrameStartTime.current != null) {
            if (time - currentFrameStartTime.current > 250) {
                setFrame((prevFrame) => (prevFrame + 1) % 4)
                currentFrameStartTime.current = time
            }
        } else {
            currentFrameStartTime.current = time
        }
        frameRequest.current = requestAnimationFrame(animate)
    }

    React.useEffect(() => {
        frameRequest.current = requestAnimationFrame(animate)
        return () => {
            if (frameRequest.current != null) cancelAnimationFrame(frameRequest.current)
        }
    }, [])

    return (
        <svg width={50} height={50} role="img" aria-label="loading" viewBox="0 0 39 25" {...rest}>
            {/* Gray background cells */}
            <g fill="#34363A">
                <path d="m13.948 0.43726h-5.0748c-1.246 0-2.256 1.0137-2.256 2.2641 0 1.2504 1.0101 2.2641 2.256 2.2641h5.0748c1.246 0 2.256-1.0137 2.256-2.2641 0-1.2504-1.01-2.2641-2.256-2.2641z" />
                <path d="m29.71 0.43726h-5.0748c-1.2459 0-2.256 1.0137-2.256 2.2641 0 1.2504 1.0101 2.2641 2.256 2.2641h5.0748c1.246 0 2.256-1.0137 2.256-2.2641 0-1.2504-1.01-2.2641-2.256-2.2641z" />
                <path d="m16.332 6.9539h-9.6145c-1.246 0-2.256 1.0137-2.256 2.2641s1.01 2.2641 2.256 2.2641h9.6145c1.2459 0 2.256-1.0137 2.256-2.2641s-1.0101-2.2641-2.256-2.2641z" />
                <path d="m22.872 11.481h9.0005c1.246 0 2.256-1.0137 2.256-2.2642 0-1.2504-1.01-2.2641-2.256-2.2641h-9.0005c-1.246 0-2.2561 1.0137-2.2561 2.2641 0 1.2504 1.0101 2.2642 2.2561 2.2642z" />
                <path d="m7.5807 20.183h-5.2582c-1.246 0-2.256 1.0137-2.256 2.2641 0 1.2505 1.0101 2.2641 2.256 2.2641h5.2582c1.246 0 2.256-1.0136 2.256-2.2641 0-1.2504-1.0101-2.2641-2.256-2.2641z" />
                <path d="m31.099 24.71h5.2583c1.2459 0 2.256-1.0137 2.256-2.2641s-1.0101-2.2641-2.256-2.2641h-5.2583c-1.2459 0-2.256 1.0137-2.256 2.2641s1.0101 2.2641 2.256 2.2641z" />
                <path d="m21.466 20.167h-4.2804c-1.246 0-2.256 1.0137-2.256 2.2641s1.01 2.2641 2.256 2.2641h4.2804c1.246 0 2.256-1.0137 2.256-2.2641s-1.01-2.2641-2.256-2.2641z" />
                <path d="m9.5383 13.666h-5.0635c-1.246 0-2.256 1.0136-2.256 2.2641 0 1.2504 1.0101 2.2641 2.256 2.2641h5.0635c1.2459 0 2.256-1.0137 2.256-2.2641 0-1.2505-1.0101-2.2641-2.256-2.2641z" />
                <path d="m29.054 18.194h5.0635c1.246 0 2.256-1.0136 2.256-2.2641 0-1.2504-1.01-2.2641-2.256-2.2641h-5.0635c-1.2459 0-2.256 1.0137-2.256 2.2641 0 1.2505 1.0101 2.2641 2.256 2.2641z" />
                <path d="m23.094 13.652h-7.5347c-1.246 0-2.2561 1.0137-2.2561 2.2641 0 1.2505 1.0101 2.2641 2.2561 2.2641h7.5347c1.246 0 2.2561-1.0136 2.2561-2.2641 0-1.2504-1.0101-2.2641-2.2561-2.2641z" />
            </g>

            {/* Frame 1: left side colored */}
            <g
                className={classNames(
                    'transition-opacity duration-[50ms]',
                    frame !== 1 && 'opacity-0'
                )}
            >
                <path
                    fill={cyan}
                    d="m13.948 0.43726h-5.0748c-1.246 0-2.256 1.0137-2.256 2.2641 0 1.2504 1.0101 2.2641 2.256 2.2641h5.0748c1.246 0 2.256-1.0137 2.256-2.2641 0-1.2504-1.01-2.2641-2.256-2.2641z"
                />
                <path
                    fill={blue}
                    d="m16.332 6.9539h-9.6145c-1.246 0-2.256 1.0137-2.256 2.2641s1.01 2.2641 2.256 2.2641h9.6145c1.2459 0 2.256-1.0137 2.256-2.2641s-1.0101-2.2641-2.256-2.2641z"
                />
                <path
                    fill={pink}
                    d="m7.5807 20.183h-5.2582c-1.246 0-2.256 1.0137-2.256 2.2641 0 1.2505 1.0101 2.2641 2.256 2.2641h5.2582c1.246 0 2.256-1.0136 2.256-2.2641 0-1.2504-1.0101-2.2641-2.256-2.2641z"
                />
                <path
                    fill={purple}
                    d="m9.5383 13.666h-5.0635c-1.246 0-2.256 1.0136-2.256 2.2641 0 1.2504 1.0101 2.2641 2.256 2.2641h5.0635c1.2459 0 2.256-1.0137 2.256-2.2641 0-1.2505-1.0101-2.2641-2.256-2.2641z"
                />
            </g>

            {/* Frame 2: middle colored */}
            <g
                className={classNames(
                    'transition-opacity duration-[50ms]',
                    frame !== 2 && 'opacity-0'
                )}
            >
                <path
                    fill={cyan}
                    d="m13.948 0.43726h-5.0748c-1.246 0-2.256 1.0137-2.256 2.2641 0 1.2504 1.0101 2.2641 2.256 2.2641h5.0748c1.246 0 2.256-1.0137 2.256-2.2641 0-1.2504-1.01-2.2641-2.256-2.2641z"
                />
                <path
                    fill={blue}
                    d="m16.332 6.9539h-9.6145c-1.246 0-2.256 1.0137-2.256 2.2641s1.01 2.2641 2.256 2.2641h9.6145c1.2459 0 2.256-1.0137 2.256-2.2641s-1.0101-2.2641-2.256-2.2641z"
                />
                <path
                    fill={pink}
                    d="m21.466 20.167h-4.2804c-1.246 0-2.256 1.0137-2.256 2.2641s1.01 2.2641 2.256 2.2641h4.2804c1.246 0 2.256-1.0137 2.256-2.2641s-1.01-2.2641-2.256-2.2641z"
                />
                <path
                    fill={purple}
                    d="m23.094 13.652h-7.5347c-1.246 0-2.2561 1.0137-2.2561 2.2641 0 1.2505 1.0101 2.2641 2.2561 2.2641h7.5347c1.246 0 2.2561-1.0136 2.2561-2.2641 0-1.2504-1.0101-2.2641-2.2561-2.2641z"
                />
                <path
                    fill={cyan}
                    d="m29.71 0.43726h-5.0748c-1.2459 0-2.256 1.0137-2.256 2.2641 0 1.2504 1.0101 2.2641 2.256 2.2641h5.0748c1.246 0 2.256-1.0137 2.256-2.2641 0-1.2504-1.01-2.2641-2.256-2.2641z"
                />
                <path
                    fill={blue}
                    d="m22.872 11.481h9.0005c1.246 0 2.256-1.0137 2.256-2.2642 0-1.2504-1.01-2.2641-2.256-2.2641h-9.0005c-1.246 0-2.2561 1.0137-2.2561 2.2641 0 1.2504 1.0101 2.2642 2.2561 2.2642z"
                />
            </g>

            {/* Frame 3: right side colored */}
            <g
                className={classNames(
                    'transition-opacity duration-[50ms]',
                    frame !== 3 && 'opacity-0'
                )}
            >
                <path
                    fill={cyan}
                    d="m29.71 0.43726h-5.0748c-1.2459 0-2.256 1.0137-2.256 2.2641 0 1.2504 1.0101 2.2641 2.256 2.2641h5.0748c1.246 0 2.256-1.0137 2.256-2.2641 0-1.2504-1.01-2.2641-2.256-2.2641z"
                />
                <path
                    fill={blue}
                    d="m22.872 11.481h9.0005c1.246 0 2.256-1.0137 2.256-2.2642 0-1.2504-1.01-2.2641-2.256-2.2641h-9.0005c-1.246 0-2.2561 1.0137-2.2561 2.2641 0 1.2504 1.0101 2.2642 2.2561 2.2642z"
                />
                <path
                    fill={purple}
                    d="m29.054 18.194h5.0635c1.246 0 2.256-1.0136 2.256-2.2641 0-1.2504-1.01-2.2641-2.256-2.2641h-5.0635c-1.2459 0-2.256 1.0137-2.256 2.2641 0 1.2505 1.0101 2.2641 2.256 2.2641z"
                />
                <path
                    fill={pink}
                    d="m31.099 24.71h5.2583c1.2459 0 2.256-1.0137 2.256-2.2641s-1.0101-2.2641-2.256-2.2641h-5.2583c-1.2459 0-2.256 1.0137-2.256 2.2641s1.0101 2.2641 2.256 2.2641z"
                />
            </g>
        </svg>
    )
}
